Conversation
cb08c65 to
0040099
Compare
dgarske
left a comment
There was a problem hiding this comment.
CI is unhappy with some of the implicit casts I think:
from wolfcrypt/src/wc_mlkem.c:66:
wolfcrypt/src/wc_mlkem.c: In function 'wc_MlKemKey_MakeKeyWithRandom':
wolfcrypt/src/wc_mlkem.c:519:53: error: conversion to 'long unsigned int' from 'int' may change the sign of the result [-Werror=sign-conversion]
519 | e = (sword16*)XMALLOC((k + 1) * k * MLKEM_N * sizeof(sword16),
| ^
./wolfssl/wolfcrypt/types.h:790:33: note: in definition of macro 'XMALLOC'
790 | wolfSSL_Malloc((s)))
| ^
wolfcrypt/src/wc_mlkem.c:560:22: error: conversion from 'int' to 'byte' {aka 'unsigned char'} may change value [-Werror=conversion]
560 | buf[0] = k;
| ^
wolfcrypt/src/wc_mlkem.c: In function 'mlkemkey_encapsulate':
wolfcrypt/src/wc_mlkem.c:852:42: error: conversion to 'int' from 'unsigned int' may change the sign of the result [-Werror=sign-conversion]
852 | ret = mlkem_get_noise(&key->prf, k, y, e1, e2, r);
| ^
Yeah I already talked to @SparkiDev about these and I still have to fix them (trying to fix the other failing tests first). The ML-KEM source files haven't yet been under test with these conversion checks. |
5e3b1e9 to
644f303
Compare
9e0f2fc to
9124900
Compare
6657e7d to
def2516
Compare
|
I added a commit to incorporate the feedback of @SparkiDev as well as one to add test coverage for #9777. |
|
Jenkins retest this please - logs gone |
|
Jenkins retest this please |
* Enable ML-KEM by default * Only allow three to-be-standardized hybrid PQ/T combinations by default * Use X25519MLKEM768 as the default KeyShare in the ClientHello (if user does not override that) * Disable standalone ML-KEM in supported groups by default (enable with --enable-tls-mlkem-standalone) * Disable extra OQS-based hybrid PQ/T curves by default and gate behind --enable-experimental (enable with --enable-extra-pqc-hybrids) * Reorder the SupportedGroups extension to reflect the preferences * Reorder the preferredGroup array to also reflect the same preferences * Enable DTLS1.3 ClientHello fragmentation by default when both DTLS1.3 and ML-KEM are enabled * Fix memory leak in TLS server PQC handling in case of ECH * Ensure PQ/T hybrids are properly tested in unit tests * Increase static memory buffer sizes to account for ML-KEM heap usage * Add async support for ML-KEM hybrids
Also fix minor problems found with these tests
* fix -Wconversion warnings * allow APIs without RNG usage in case WC_NO_RNG is defined
|
I squashed the last three commits regarding the ML-KEM |
|
@julek-wolfssl @anhu @dgarske can you please review? |
| #if defined(HAVE_PQC) && defined(WOLFSSL_DTLS13) && \ | ||
| !defined(WOLFSSL_DTLS_CH_FRAG) | ||
| #warning "Using DTLS 1.3 + pqc without WOLFSSL_DTLS_CH_FRAG will probably" \ | ||
| "fail.Use --enable-dtls-frag-ch to enable it." | ||
| #if defined(HAVE_PQC) && defined(WOLFSSL_HAVE_MLKEM) && \ | ||
| defined(WOLFSSL_DTLS13) && !defined(WOLFSSL_DTLS_CH_FRAG) | ||
| #define WOLFSSL_DTLS_CH_FRAG |
There was a problem hiding this comment.
WOLFSSL_DTLS_CH_FRAG is our hack to get PQC working with DTLS. I'm not sure that quietly enabling it is a good idea. It may clash with implementations that solve large key shares differently (eg. jumbo packets, IP fragmentation). @rizlik thoughts?
There was a problem hiding this comment.
I think it's OK: on the client-side we fully respect the protocol and on the server-side we are slightly less pickier compared to not having that enabled, but still on the safe side.
Even with option enabled, the server will still refuse messages that are valid per RFC, but impossible to handle statelessly: CH0 fragmented or CH1 fragmented but with cookie extension on the second fragment.
In the future we might want to allow users to drop statelessness for performance (removing both the needs of an extra round with HRR and/or interop (CH fragmented without having the cookie extension in the first fragment from other implementations). But for now, I don't see problems enabling it. We would fail interop with library that do not respect our model regardless.
| /* Re-enable HRR cookie to account for potential CH fragmentation */ | ||
| ExpectIntEQ(wolfSSL_send_hrr_cookie(ssl_s, NULL, 0), WOLFSSL_SUCCESS); | ||
|
|
There was a problem hiding this comment.
We shouldn't promote changing settings in the middle of a connection. Maybe limiting the ciphersuites to classical only is a better approach.
| if (ssl->hrr_keyshare_group != 0) { | ||
| if (ssl->hrr_keyshare_group != 0 && seenGroupsCnt > 0) { |
There was a problem hiding this comment.
Is an empty key share not an error? Why success on seenGroupsCnt == 0?
| #ifdef WOLFSSL_DTLS_CH_FRAG | ||
| { | ||
| /* Get the chosen group. If ret == 0 here, we are sure that the | ||
| * extension is present. */ | ||
| TLSX* ksExt = TLSX_Find(parsedExts, TLSX_KEY_SHARE); | ||
| KeyShareEntry* kse = (KeyShareEntry*)ksExt->data; | ||
| if (WOLFSSL_NAMED_GROUP_IS_PQC(kse->group) || | ||
| WOLFSSL_NAMED_GROUP_IS_PQC_HYBRID(kse->group)) { | ||
| /* Allow fragmentation of the second ClientHello due to the | ||
| * large PQC key share. */ | ||
| wolfSSL_dtls13_allow_ch_frag((WOLFSSL*)ssl, 1); | ||
| } | ||
| } | ||
| #endif |
There was a problem hiding this comment.
Again, I don't know if enabling this quietly for the user is safe. We should respect the API contract we have with users where this needs to be explicitly enabled. There are DoS considerations. @rizlik
| if (WOLFSSL_NAMED_GROUP_IS_PQC(kse->group) || | ||
| WOLFSSL_NAMED_GROUP_IS_PQC_HYBRID(kse->group)) { |
There was a problem hiding this comment.
| if (WOLFSSL_NAMED_GROUP_IS_PQC(kse->group) || | |
| WOLFSSL_NAMED_GROUP_IS_PQC_HYBRID(kse->group)) { | |
| if (kse != NULL && (WOLFSSL_NAMED_GROUP_IS_PQC(kse->group) || | |
| WOLFSSL_NAMED_GROUP_IS_PQC_HYBRID(kse->group))) { |
This PR enables the standardized PQC algorithm ML-KEM (FIPS203) by default.
ML-KEM enabled by default
The ML-KEM algorithm is now enabled by default when building the library. This results in the same behavior as currently passing
--enable-mlkem=yesto configure. When a specialized configuration for ML-KEM is required,--enable-mlkem=<desired options>is still possible as normal.Algorithm changes
Prior to this PR, when ML-KEM has been enabled, all available groups that “contain” ML-KEM have been enabled to be used for the TLS key exchange. This behavior is now changed to the following:
Groups enabled by default:
X25519MLKEM768,SECP256R1MLKEM768,SECP384R1MLKEM1024; these are the to-be-standardized hybrid PQ/T combinations from draft-ietf-tls-ecdhe-mlkem. These hybrids are considered “most secure” by the community and are already widely deployed in the web, especiallyX25519MLKEM768(e.g., see here).Currently not enabled by default: all standalone ML-KEM groups (
MLKEM512,MLKEM768,MLKEM1024from draft-ietf-tls-mlkem), as standalone ML-KEM usage is not widely deployed presently and also considered “more dangerous”.Some “extra” hybrid PQ/T groups with different combinations of ML-KEM and ECC groups, which are defined by the OQS project, are also disabled by default (
SECP256R1MLKEM512,SECP384R1MLKEM768,SECP521R1MLKEM1024,X25519MLKEM512).Next to the default enablement of these groups, the “ preference “ of these groups has also been increased. On the client side, if no specific group for the key share is set,
X25519MLKEM768is now selected as the default one when Curve25519 is enabled. Otherwise,SECP384R1MLKEM1024is used (if hybrids are not disabled). On the server side, when a client presents more than one key share in its ClientHello, a hybrid one is now also preferred to a traditional-only one.This now also reflects the behavior of OpenSSL since version 3.5.
Build system changes
To reflect the changes from above, changes in the build system have been performed.
In the autoconf setup,
--enable-mlkemis now set toyesby default. Furthermore, the following three new options are added:--enable-pqc-hybrids(on by default): This enables (or disables) the three to-be-standardized hybrid PQ/T combinations.--enable-tls-mlkem-standalone(off by default): This enables the standalone usage of ML-KEM. When enabled, the three standalone groups are advertised in the SupportedGroups extension by the client. When the hybrid groups from above are disabled, thenMLKEM1024is also selected as the default in the key share sent by the client. Otherwise, the hybrids are still ranked higher.--enable-extra-pqc-hybrids(off by default, requires --enable-experimentalin addition): This enables the extra PQ/T groups from the OQS project.In addition to these new options, some dependencies of ML-KEM are now also enabled by default, namely SHA3 (
--enable-sha3), SHAKE128 (--enable-shake128) and SHAKE256 (--enable-shake128).Furthermore, when DTLS 1.3 is enabled, then ClientHello fragmentation (
--enable-dtls-frag-ch) is now also enabled by default, as most PQ/T and standalone PQC key shares require fragmentation.All these options and changes have also been applied to CMake builds and to Zephyr, too.
Runtime changes
The order of the algorithms has been changed in both the SupportedGroups extension sent by the client as well as in the
preferredGrouparray to rank the three PQ/T hybrids highest. The standalone ML-KEM groups are added based on their achieved security strength into the list, but always before their matching traditional counterparts (to prioritize the PQC groups over traditional ones in case hybrids are disabled).For DTLS 1.3, the server now also automatically enables ClientHello fragmentation when the client sends a PQ/T or PQC key share (which requires a HelloRetryRequest and a second ClientHello).
For async crypto support, hybrid PQ/T groups are now also handled properly on both the client and server sides (only the ECC part of the hybrid combination is handled asynchronously, as ML-KEM currently lacks async support).
Tests
In the test infrastructure, all the new options are added to be tested. Furthermore, existing tests have been adapted to incorporate the different resource usage for the ML-KEM groups (more memory usage for static memory cases, different fragmentation in case of DTLS, manually set specific groups that are required in some tests, ...).
Moreover, the general testing of PQC and the PQ/T hybrids has been extended to cover all groups and more edge-cases.
Other changes
wc_mlkem.candwc_mlkem_poly.chave been updated to fix -Wconversion warnings (now also tested in CI for ML-KEM).--disable-rng), ML-KEM is now usable only with limited functionality. Mainly, key generation and encapsulation are only possible with a given seed. This is also handled in the unit tests.